package com.zhuhjay.common.utils;

import com.alibaba.fastjson.JSONObject;

import javax.servlet.http.HttpServletRequest;
import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.net.InetAddress;
import java.net.URL;
import java.net.URLConnection;
import java.util.Map;

/**
 * 处理客户端信息的工具
 * 获取IP, 转换IP为地理位置等
 * @author ZhuHJay
 * @date 2022/3/26 10:38
 */
public class ClientUtils {

    /** 腾讯位置服务 Key **/
    private static final String TENCENT_KEY = "BBQBZ-U5VKX-UFT45-ZNGNN-V6QEQ-QKBUU";

    /** 判断请求是否成功 **/
    public static Integer requestStatus(Integer status){
        return status / 100 == 2 ? 1 : 0;
    }

    /** 获取请求用户的ip地址 **/
    public static String getIpAddress(HttpServletRequest request) {
        final String localAddress = "127.0.0.1";
        String ipAddress;
        try {
            ipAddress = request.getHeader("x-forwarded-for");
            if (ipAddress == null || ipAddress.length() == 0 || "unknown".equalsIgnoreCase(ipAddress)) {
                ipAddress = request.getHeader("Proxy-Client-IP");
            }
            if (ipAddress == null || ipAddress.length() == 0 || "unknown".equalsIgnoreCase(ipAddress)) {
                ipAddress = request.getHeader("WL-Proxy-Client-IP");
            }
            if (ipAddress == null || ipAddress.length() == 0 || "unknown".equalsIgnoreCase(ipAddress)) {
                ipAddress = request.getRemoteAddr();
                if ( localAddress.equals(ipAddress) ) {
                    // 根据网卡取本机配置的IP
                    InetAddress inet = null;
                    try {
                        inet = InetAddress.getLocalHost();
                    } catch (Exception e) {
                        e.printStackTrace();
                    }
                    assert inet != null;
                    ipAddress = inet.getHostAddress();
                }
            }
            // 对于通过多个代理的情况，第一个IP为客户端真实IP,多个IP按照','分割
            // "***.***.***.***".length()
            if (ipAddress != null && ipAddress.length() > 15) {
                // = 15
                if (ipAddress.indexOf(",") > 0) {
                    ipAddress = ipAddress.substring(0, ipAddress.indexOf(","));
                }
            }
        } catch (Exception e) {
            ipAddress = localAddress;
            e.printStackTrace();
        }
        return "0:0:0:0:0:0:0:1".equals(ipAddress) ? localAddress : ipAddress;
    }

        /** 通过ip获取城市地理信息 **/
    public static String getCityInfo(String ip)  {
        final String successMessage = "Success";
        if ("127.0.0.1".equals(ip)) {
            return "内网IP";
        }
        String s = sendHttpGet(ip);
        // 将响应的JSON数据转换为Map对象
        Map map = JSONObject.parseObject(s, Map.class);
        String message = (String) map.get("message");
        if( successMessage.equals(message) ){
            Map result = (Map) map.get("result");
            Map addressInfo = (Map) result.get("ad_info");
            String nation = (String) addressInfo.get("nation");
            String province = (String) addressInfo.get("province");
            String city = (String) addressInfo.get("city");
            return nation + "-" + province + "-" + city;
        }
        return message;
    }

    /** 访问腾讯位置服务获取ip的地理位置 **/
    private static String sendHttpGet(String ip) {
        StringBuilder result = new StringBuilder();
        BufferedReader in = null;
        try {
            String urlNameString = "https://apis.map.qq.com/ws/location/v1/ip?ip="+ip+"&key="+TENCENT_KEY;
            URL realUrl = new URL(urlNameString);
            // 打开和URL之间的连接
            URLConnection connection = realUrl.openConnection();
            // 设置通用的请求属性
            connection.setRequestProperty("accept", "*/*");
            connection.setRequestProperty("connection", "Keep-Alive");
            connection.setRequestProperty("user-agent",
                    "Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1;SV1)");
            // 建立实际的连接
            connection.connect();
            // 定义 BufferedReader输入流来读取URL的响应
            in = new BufferedReader(new InputStreamReader(
                    connection.getInputStream()));
            String line;
            while ((line = in.readLine()) != null) {
                result.append(line);
            }
        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            try {
                if (in != null) {
                    in.close();
                }
            } catch (Exception e2) {
                e2.printStackTrace();
            }
        }
        return result.toString();
    }

}
